import 'dart:math';

import 'package:collection/collection.dart';
import 'package:flutter/material.dart';
import 'package:flutter/services.dart';
import 'package:flutter_2b_client/utils/StringUtils.dart';
import 'package:flutter_hooks/flutter_hooks.dart';
import 'package:go_router/go_router.dart';

import '../apis/FactoryApi.dart';
import '../apis/GoodsApi.dart';
import '../apis/GoodsBrandApi.dart';
import '../apis/GoodsCategoryApi.dart';
import '../model/IntIdAndName.dart';
import '../pages/ScanBarcodePage.dart';
import '../utils/SingleUnitPeriod.dart';
import 'GoodsUnitEditor.dart';
import 'LoadableIconButton.dart';
import 'LoadingButton.dart';

class EditGoodsForm extends HookWidget {
  final String? name;
  final String? barcode;
  final double? price;
  final int? amount;
  final int? goodsBrandId;
  final int? goodsCategoryId;
  final String? boxSpecification;
  final List<GoodsUnitFormData>? units;
  final String? expressionPeriod;
  final String? recordFilingNumber;
  final String? registrationCertificateNumber;
  final String? note;
  final String? executiveStandard;

  final Future<void> Function(AddGoodsRequest request) onSave;

  EditGoodsForm({
    Key? key,
    required this.onSave,
    this.name,
    this.barcode,
    this.price,
    this.amount,
    this.goodsBrandId,
    this.goodsCategoryId,
    this.boxSpecification,
    this.units,
    this.recordFilingNumber,
    this.expressionPeriod,
    this.registrationCertificateNumber,
    this.note,
    this.executiveStandard,
  }) : super(key: key);
  final _formKey = GlobalKey<FormState>();

  @override
  Widget build(BuildContext context) {
    final nameState = useState(name ?? "");
    final barcodeState = useState(barcode ?? "");
    var barcodeTextEditingController = useTextEditingController(text: barcode);
    final priceState = useState<double?>(price);
    final amountState = useState<int>(amount ?? 0);
    final goodsBrandIdState = useState<int?>(goodsBrandId);
    final goodsCategoryIdState = useState<int?>(goodsCategoryId);
    final boxSpecificationState = useState(boxSpecification ?? "");
    final registrationCertificateNumberState =
        useState(registrationCertificateNumber ?? "");
    final recordFilingNumberState = useState(recordFilingNumber ?? "");
    final executiveStandardState = useState(executiveStandard??"");
    useState(executiveStandard ?? "");
    final noteState = useState(note ?? "");
    var singleUnitPeriodState = useState<SingleUnitPeriod>(
        expressionPeriod != null
            ? SingleUnitPeriod.parse(expressionPeriod!)
            : SingleUnitPeriod(PeriodUnit.year, 1));
    var goodsBrandsState = useState<List<IntIdAndName>>([]);
    useEffect(
      () {
        goodsBrandApi
            .getAllGoodsBrands()
            .then((value) => goodsBrandsState.value = value);
        return null;
      },
      [],
    );

    var goodsCategoriesState = useState<List<IntIdAndName>>([]);
    useEffect(
      () {
        goodsCategoryApi
            .getAllGoodsCategories()
            .then((value) => goodsCategoriesState.value = value);
        return null;
      },
      [],
    );

    var goodsFactoriesState = useState<List<IntIdAndName>>([]);
    useEffect(
      () {
        factoryApi
            .getAllFactories()
            .then((value) => goodsFactoriesState.value = value);
        return null;
      },
      [],
    );

    var goodsUnitsState = useState<List<GoodsUnitFormData>>(units ?? []);
    return Stack(
      children: [
        Positioned.fill(
          top: 0,
          bottom: 86,
          child: SingleChildScrollView(
            child: Form(
              key: _formKey,
              child: Padding(
                padding: const EdgeInsets.symmetric(horizontal: 16),
                child: Column(
                  crossAxisAlignment: CrossAxisAlignment.start,
                  children: [
                    TextFormField(
                      validator: (value) {
                        if (value == null || value.isEmpty) {
                          return "请输入商品名称";
                        }
                        return null;
                      },
                      onChanged: (value) {
                        nameState.value = value.trim();
                      },
                      initialValue: nameState.value,
                      decoration: const InputDecoration(label: Text("商品名称")),
                    ),
                    Row(
                      mainAxisAlignment: MainAxisAlignment.spaceBetween,
                      crossAxisAlignment: CrossAxisAlignment.end,
                      children: [
                        Expanded(
                          child: TextFormField(
                            validator: (value) {
                              if (value == null || value.isEmpty) {
                                return "请输入商品条码";
                              }
                              return null;
                            },
                            controller: barcodeTextEditingController,
                            onChanged: (value) {
                              barcodeState.value = value.trim();
                            },
                            decoration: const InputDecoration(
                              label: Text("商品条码"),
                            ),
                            keyboardType: TextInputType.number,
                          ),
                        ),
                        LoadableIconButton(
                          onPressed: () async {
                            var barcode = await context.push(ScanBarcodePage.path);
                            if (barcode != null) {
                              barcodeTextEditingController.text = barcode as String;
                            }
                          },
                          icon: const Icon(Icons.document_scanner),
                        ),
                      ],
                    ),
                    Row(
                      crossAxisAlignment: CrossAxisAlignment.start,
                      children: [
                        Expanded(
                          child: TextFormField(
                            validator: (value) {
                              if (value == null || value.isEmpty) {
                                return "请输入零售价";
                              }
                              return null;
                            },
                            initialValue: priceState.value?.toString(),
                            onChanged: (value) {
                              priceState.value = double.tryParse(value) ?? 0;
                            },
                            decoration: const InputDecoration(
                              label: Text("零售价"),
                            ),
                            keyboardType: TextInputType.number,
                          ),
                        ),
                        const SizedBox(
                          width: 8,
                        ),
                        Expanded(
                          child: TextFormField(
                            validator: (value) {
                              if (value == null || value.isEmpty) {
                                return "请输入库存";
                              }
                              return null;
                            },
                            initialValue: amountState.value.toString(),
                            onChanged: (value) {
                              amountState.value = int.tryParse(value) ?? 0;
                            },
                            decoration: const InputDecoration(
                              label: Text("库存"),
                            ),
                            keyboardType: TextInputType.number,
                          ),
                        ),
                      ],
                    ),
                    Row(
                      mainAxisAlignment: MainAxisAlignment.spaceBetween,
                      crossAxisAlignment: CrossAxisAlignment.center,
                      children: [
                        Expanded(
                          child: DropdownButtonFormField<IntIdAndName>(
                            value: goodsBrandsState.value.firstWhereOrNull(
                                (element) => element.id == goodsBrandIdState.value),
                            itemHeight: null,
                            items: goodsBrandsState.value
                                .map(
                                  (e) =>
                                      DropdownMenuItem(value: e, child: Text(e.name)),
                                )
                                .toList(),
                            onChanged: (value) {
                              goodsBrandIdState.value = value?.id;
                            },
                            isExpanded: true,
                            decoration: const InputDecoration(
                              label: Text("品牌"),
                            ),
                          ),
                        ),
                        const SizedBox(
                          width: 8,
                        ),
                        Expanded(
                          child: DropdownButtonFormField<IntIdAndName>(
                            value: goodsCategoriesState.value.firstWhereOrNull(
                                (element) => element.id == goodsCategoryIdState.value),
                            itemHeight: null,
                            items: goodsCategoriesState.value
                                .map(
                                  (e) =>
                                      DropdownMenuItem(value: e, child: Text(e.name)),
                                )
                                .toList(),
                            onChanged: (value) {
                              goodsCategoryIdState.value = value?.id;
                            },
                            isExpanded: true,
                            decoration: const InputDecoration(
                              label: Text("分类"),
                            ),
                          ),
                        ),
                      ],
                    ),
                    TextFormField(
                      onChanged: (value) {
                        boxSpecificationState.value = value.trim();
                      },
                      initialValue: boxSpecificationState.value,
                      decoration: const InputDecoration(
                        label: Text("箱规"),
                      ),
                    ),
                    Row(
                      mainAxisSize: MainAxisSize.min,
                      crossAxisAlignment: CrossAxisAlignment.end,
                      children: [
                        SizedBox(
                          width: 88,
                          child: TextFormField(
                            onChanged: (value) {
                              singleUnitPeriodState.value = SingleUnitPeriod(
                                  singleUnitPeriodState.value.unit,
                                  max(int.tryParse(value) ?? 1, 1));
                            },
                            inputFormatters: [
                              FilteringTextInputFormatter.digitsOnly,
                            ],
                            initialValue: singleUnitPeriodState.value.value.toString(),
                            decoration: const InputDecoration(
                              label: Text("保质期"),
                            ),
                            keyboardType: TextInputType.number,
                          ),
                        ),
                        const SizedBox(
                          width: 4,
                        ),
                        SizedBox(
                          width: 56,
                          child: DropdownButtonFormField<PeriodUnit>(
                            value: singleUnitPeriodState.value.unit,
                            itemHeight: null,
                            items: PeriodUnit.values
                                .map(
                                  (e) => DropdownMenuItem(
                                      value: e, child: Text(e.displayName)),
                                )
                                .toList(),
                            onChanged: (value) {
                              singleUnitPeriodState.value = SingleUnitPeriod(
                                  value ?? PeriodUnit.year,
                                  singleUnitPeriodState.value.value);
                            },
                            isExpanded: true,
                            hint: const Text("单位"),
                          ),
                        ),
                      ],
                    ),
                    GoodsUnitEditor(
                      value: goodsUnitsState.value,
                      onChange: (List<GoodsUnitFormData> value) {
                        goodsUnitsState.value = value;
                      },
                    ),
                    TextFormField(
                      onChanged: (value) {
                        recordFilingNumberState.value = value.trim();
                      },
                      initialValue: recordFilingNumberState.value,
                      decoration: const InputDecoration(
                        label: Text("备案编号/产品的执行标准编号"),
                      ),
                    ),
                    TextFormField(
                      onChanged: (value) {
                        registrationCertificateNumberState.value = value.trim();
                      },
                      initialValue: registrationCertificateNumberState.value,
                      decoration: const InputDecoration(
                        label: Text("注册证编号"),
                      ),
                    ),
                    TextFormField(
                      onChanged: (value) {
                        executiveStandardState.value = value.trim();
                      },
                      initialValue: executiveStandardState.value,
                      decoration: const InputDecoration(
                        label: Text("执行标准"),
                      ),
                    ),
                    TextFormField(
                      onChanged: (value) {
                        noteState.value = value.trim();
                      },
                      initialValue: noteState.value,
                      decoration: const InputDecoration(
                        label: Text("备注"),
                      ),
                      maxLength: 125,
                      maxLines: 3,
                    ),
                  ],
                ),
              ),
            ),
          ),
        ),
        Positioned(
          bottom: 24,
          left: 24,
          right: 24,
          child: LoadingButton(
            child: const Text("保存"),
            onPressed: () async {
              if (_formKey.currentState?.validate() == true) {
                var request = AddGoodsRequest(
                  name: nameState.value,
                  amount: amountState.value,
                  price: priceState.value!,
                  barcode: barcodeState.value,
                  categoryId: goodsCategoryIdState.value,
                  brandId: goodsBrandIdState.value,
                  boxSpecification: boxSpecificationState.value.nullIfEmpty,
                  units: goodsUnitsState.value
                      .map((e) => e.toRequest())
                      .toList(),
                  recordFilingNumber: recordFilingNumberState.value.nullIfEmpty,
                  registrationCertificateNumber:
                  registrationCertificateNumberState.value.nullIfEmpty,
                  expressionPeriod: singleUnitPeriodState.value.value > 0
                      ? singleUnitPeriodState.value.toString()
                      : null,
                  note: noteState.value,
                  executiveStandard: executiveStandardState.value.nullIfEmpty
                );
                await onSave(request);
                if (context.mounted) {
                  context.pop(request);
                }
              }
            },
          ),
        ),
      ],
    );
  }
}
